<!DOCTYPE html>

<head>
	<meta http-equiv="Content-type" content="text/html; charset=utf-8">
	<title>Limit drag and drop dates</title>
	<script src="../../codebase/dhtmlxgantt.js?v=7.1.7"></script>
	<link rel="stylesheet" href="../../codebase/dhtmlxgantt.css?v=7.1.7">
	<style>
		html,
		body {
			height: 100%;
			padding: 0px;
			margin: 0px;
			overflow: hidden;
		}
	</style>
</head>

<body>
	<div id="gantt_here" style='width:100%; height:100%;'></div>
	<script>


		gantt.templates.task_class = function (st, end, item) {
			return gantt.getChildren(item.id).length ? "gantt_project" : "";
		};
		gantt.init("gantt_here");

		function limitMoveLeft(task, limit) {
			var dur = task.end_date - task.start_date;
			task.end_date = new Date(limit.end_date);
			task.start_date = new Date(+task.end_date - dur);
		}

		function limitMoveRight(task, limit) {
			var dur = task.end_date - task.start_date;
			task.start_date = new Date(limit.start_date);
			task.end_date = new Date(+task.start_date + dur);
		}

		function limitResizeLeft(task, limit) {
			task.end_date = new Date(limit.end_date);
		}

		function limitResizeRight(task, limit) {
			task.start_date = new Date(limit.start_date)
		}

		gantt.attachEvent("onTaskDrag", function (id, mode, task, original, e) {
			var parent = task.parent ? gantt.getTask(task.parent) : null,
				children = gantt.getChildren(id),
				modes = gantt.config.drag_mode;

			var limitLeft = null,
				limitRight = null;

			if (!(mode == modes.move || mode == modes.resize)) return;

			if (mode == modes.move) {
				limitLeft = limitMoveLeft;
				limitRight = limitMoveRight;
			} else if (mode == modes.resize) {
				limitLeft = limitResizeLeft;
				limitRight = limitResizeRight;
			}

			//check parents constraints
			if (parent && +parent.end_date < +task.end_date) {
				limitLeft(task, parent);
			}
			if (parent && +parent.start_date > +task.start_date) {
				limitRight(task, parent);
			}

			//check children constraints
			for (var i = 0; i < children.length; i++) {
				var child = gantt.getTask(children[i]);
				if (+task.end_date < +child.end_date) {
					limitLeft(task, child);
				} else if (+task.start_date > +child.start_date) {
					limitRight(task, child)
				}
			}


		});
		gantt.parse({
			data: [
				{ id: 11, text: "Project #1", start_date: "01-04-2018", duration: "11", progress: 0.6, open: true },
				{ id: 12, text: "Task #1", start_date: "03-04-2018", duration: "5", parent: "11", progress: 1, open: true },
				{ id: 13, text: "Task #2", start_date: "02-04-2018", duration: "7", parent: "11", progress: 0.5, open: true },
				{ id: 14, text: "Task #3", start_date: "02-04-2018", duration: "6", parent: "11", progress: 0.8, open: true },
				{ id: 15, text: "Task #4", start_date: "02-04-2018", duration: "6", parent: "11", progress: 0.2, open: true },
				{ id: 16, text: "Task #5", start_date: "02-04-2018", duration: "7", parent: "11", progress: 0, open: true },
				{ id: 17, text: "Task #2.1", start_date: "03-04-2018", duration: "2", parent: "13", progress: 1, open: true },
				{ id: 18, text: "Task #2.2", start_date: "06-04-2018", duration: "3", parent: "13", progress: 0.8, open: true },
				{ id: 21, text: "Task #4.1", start_date: "03-04-2018", duration: "4", parent: "15", progress: 0.5, open: true },
				{ id: 22, text: "Task #4.2", start_date: "03-04-2018", duration: "4", parent: "15", progress: 0.1, open: true },
				{ id: 23, text: "Task #4.3", start_date: "03-04-2018", duration: "5", parent: "15", progress: 0, open: true }
			]
		});
	</script>
</body>